/**
 * NSDate+GTExtension.m
 *
 * The contents of this file are subject to the Mozilla Public License Version 1.1 (the "License");
 * you may not use this file except in compliance with the License. You may obtain a copy of the License 
 * at http://www.mozilla.org/MPL/
 * Software distributed under the License is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND,
 * either express or implied. See the License for the specific language governing rights and limitations 
 * under the License.
 *
 * The Original Code is gcast-toolbox4iphone.
 *
 * The Initial Developers of the Original Code is Giannandrea Castaldi.
 */
#import "NSDate+GTExtension.h"

static const NSTimeInterval kSecondsInOneDay = 86400.0;

@implementation NSDate (GTExtension)

+ (NSDate *)today {
  return [NSDate date];
}

+ (NSDate *)tomorrow {
  return [NSDate dateWithTimeIntervalSinceNow:kSecondsInOneDay];
}

+ (NSDate *)daysAhead:(NSInteger)numOfDays {
  return [NSDate dateWithTimeIntervalSinceNow:kSecondsInOneDay*numOfDays];
}

+ (NSDate *)daysBehind:(NSInteger)numOfDays {
  return [NSDate dateWithTimeIntervalSinceNow:-kSecondsInOneDay*numOfDays];
}

+ (NSDate *)dateWithYear:(NSInteger)year month:(NSInteger)month day:(NSInteger)day {
  NSCalendar *gregorian = [[[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar] autorelease];
  NSDateComponents *components = [gregorian components:(NSYearCalendarUnit
                                                        |NSMonthCalendarUnit
                                                        |NSDayCalendarUnit
                                                        |NSHourCalendarUnit
                                                        |NSMinuteCalendarUnit
                                                        |NSSecondCalendarUnit)
                                              fromDate:[NSDate date]];
  [components setYear:year];  
  [components setMonth:month];
  [components setDay:day];
  [components setHour:0];
  [components setMinute:0];
  [components setSecond:0];
  return [gregorian dateFromComponents:components];
}

+ (NSDate *)dateWithHour:(NSInteger)hour minute:(NSInteger)minute second:(NSInteger)second {
  NSCalendar *gregorian = [[[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar] autorelease];
  NSDateComponents *components = [gregorian components:(NSYearCalendarUnit
                                                        |NSMonthCalendarUnit
                                                        |NSDayCalendarUnit
                                                        |NSHourCalendarUnit
                                                        |NSMinuteCalendarUnit
                                                        |NSSecondCalendarUnit)
                                              fromDate:[NSDate date]];
  [components setHour:hour];  
  [components setMinute:minute];
  [components setSecond:second];
  return [gregorian dateFromComponents:components];
}

+ (NSDate *)dateWithYear:(NSInteger)year month:(NSInteger)month day:(NSInteger)day hour:(NSInteger)hour minute:(NSInteger)minute second:(NSInteger)second {
  NSDateComponents *components = [[[NSDateComponents alloc] init] autorelease];
  [components setYear:year];  
  [components setMonth:month];
  [components setDay:day];
  [components setHour:hour];  
  [components setMinute:minute];
  [components setSecond:second];
  return [[NSCalendar currentCalendar] dateFromComponents:components];
}

+ (NSDate*)dateWithTimeFromSeconds:(NSTimeInterval)seconds {
  NSDate *result = [NSDate dateWithHour:0 minute:0 second:0];
  if (seconds > 0) {
    result = [NSDate dateWithHour:(seconds / SECONDS_IN_ONE_HOUR)
                           minute:(((NSUInteger)seconds) % ((NSUInteger)SECONDS_IN_ONE_HOUR)) / SECONDS_IN_ONE_MINUTE
                           second:(((NSUInteger)seconds) % ((NSUInteger)SECONDS_IN_ONE_HOUR)) % ((NSUInteger)SECONDS_IN_ONE_MINUTE)];
  }
  return result;
}

+ (NSString*)stringFromTimeInterval:(NSTimeInterval)interval {
  NSInteger ti = (NSInteger)interval;
  NSInteger seconds = ti % 60;
  NSInteger minutes = (ti / 60) % 60;
  NSInteger hours = (ti / 3600);
  return [NSString stringWithFormat:@"%02i:%02i:%02i", hours, minutes, seconds];
}

- (NSTimeInterval)timeInSeconds {
  return self.hour * SECONDS_IN_ONE_HOUR + self.minute * SECONDS_IN_ONE_MINUTE + self.second;
}

- (NSInteger)day {
  return [[[NSCalendar currentCalendar] components:NSDayCalendarUnit fromDate:self] day];
}

- (NSInteger)month {
  return [[[NSCalendar currentCalendar] components:NSMonthCalendarUnit fromDate:self] month];
}

- (NSInteger)year {
  return [[[NSCalendar currentCalendar] components:NSYearCalendarUnit fromDate:self] year];
}

- (NSInteger)hour {
  return [[[NSCalendar currentCalendar] components:NSHourCalendarUnit fromDate:self] hour];
}

- (NSInteger)minute {
  return [[[NSCalendar currentCalendar] components:NSMinuteCalendarUnit fromDate:self] minute];
}

- (NSInteger)second {
  return [[[NSCalendar currentCalendar] components:NSSecondCalendarUnit fromDate:self] second];
}

- (NSDate *)daysAhead:(NSInteger)numOfDays {
  NSDateComponents *offsetComponents = [[[NSDateComponents alloc] init] autorelease];
  [offsetComponents setDay:numOfDays];
  return [[NSCalendar currentCalendar] dateByAddingComponents:offsetComponents toDate:self options:0];  
}

- (NSDate *)daysBehind:(NSInteger)numOfDays {
  NSDateComponents *offsetComponents = [[[NSDateComponents alloc] init] autorelease];
  [offsetComponents setDay:-numOfDays];
  return [[NSCalendar currentCalendar] dateByAddingComponents:offsetComponents toDate:self options:0];  
}

- (NSComparisonResult)compareOnlyYearMonthDay:(NSDate *)anotherDate {
  return [[NSDate dateWithYear:self.year
                         month:self.month
                           day:self.day] compare:[NSDate dateWithYear:anotherDate.year
                                                                month:anotherDate.month
                                                                  day:anotherDate.day]];
}

- (NSComparisonResult)compareOnlyHourMinuteSecond:(NSDate *)anotherDate {
  return [[NSDate dateWithHour:self.hour
                        minute:self.minute
                        second:self.second] compare:[NSDate dateWithHour:anotherDate.hour
                                                                  minute:anotherDate.minute
                                                                  second:anotherDate.second]];
}

@end
